home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1998 January: Mac OS SDK / Dev.CD Jan 98 SDK2.toast / Development Kits (Disc 2) / QuickTime / Sample Code / QT QuickDraw 3D tracks / Code / 3DMF to Animated Camera Movie / 3dMF2AnimatedCameraMovie.c next >
Encoding:
C/C++ Source or Header  |  1997-02-26  |  8.4 KB  |  275 lines  |  [TEXT/CWIE]

  1. #include <Fonts.h>
  2. #include <Movies.h>
  3. #include <QD3D.h>
  4. #include <QD3DCamera.h>
  5. #include <QD3DTransform.h>
  6.  
  7. OSErr addTweenEntryToSample(QTAtomContainer tweenSample, long tweenID, long tweenType,
  8.             void *tweenData, long tweenDataSize);
  9.  
  10. OSErr setTweenEntryStartOffset(QTAtomContainer tweenSample, long tweenID, TimeValue startOffset);
  11.  
  12. OSErr setTweenEntryDuration(QTAtomContainer tweenSample, long tweenID, TimeValue duration);
  13.  
  14. OSErr setTweenEntryInitialConditions(QTAtomContainer tweenSample, long tweenID,
  15.             void *initialData, long initialDataSize);
  16.  
  17. OSErr addTweenEntryToInputMapEntry(QTAtomContainer inputMap, long referenceIndex, long tweenID,
  18.                 long tweenType, char *name);
  19.  
  20. void main(void)
  21. {
  22.     TQ3Point3D                        cameraFrom     = { 0.0, 0.0, 30.0 };
  23.     TQ3Point3D                        cameraTo     = { 0.0, 0.0, 0.0 };
  24.     TQ3Vector3D                        cameraUp     = { 0.0, 1.0, 0.0 };
  25.  
  26.     OSErr err = noErr;
  27.     OSType types;
  28.     StandardFileReply reply;
  29.     Movie newMovie;
  30.     ThreeDeeDescriptionHandle sampleDescription = nil;
  31.     short fref;
  32.     AliasHandle alias = nil;
  33.     long eof;
  34.     Movie theMovie;
  35.     Track threeDeeTrack, tweenTrack;
  36.     Media threeDeeMedia, tweenMedia;
  37.     FSSpec movieFSS;
  38.     short movieResRef;
  39.     QTAtomContainer tweenSample;
  40.     TQ3CameraData tweenCamera;
  41.     long referenceIndex1;
  42.     QTAtomContainer inputMap;
  43.  
  44.     InitGraf(&qd.thePort);
  45.     InitFonts();
  46.     InitWindows();
  47.     InitMenus();
  48.     TEInit();
  49.     InitDialogs(0L);
  50.     InitCursor();
  51.     MaxApplZone();
  52.  
  53.     EnterMovies();
  54.  
  55.     // ask user for a file
  56.     types = '3DMF';
  57.     StandardGetFilePreview(nil, 1, &types, &reply);
  58.     if (!reply.sfGood) return;
  59.  
  60.     // figure out the size of the file
  61.     FSpOpenDF(&reply.sfFile, fsRdPerm, &fref);
  62.     GetEOF(fref, &eof);
  63.     FSClose(fref);
  64.  
  65.     // make an alias to the file (QuickTime term: data reference)
  66.     NewAliasMinimal(&reply.sfFile, &alias);
  67.  
  68.     // make up a sample description for the 3d media
  69.     sampleDescription = (ThreeDeeDescriptionHandle)NewHandleClear(sizeof(ThreeDeeDescription));
  70.     if (err = MemError()) return;
  71.     (**sampleDescription).descSize = sizeof(ThreeDeeDescription);
  72.  
  73.     // create a movie file
  74.     FSMakeFSSpec(0, 0, "\p3D Animated Camera Movie File", &movieFSS);
  75.     err = CreateMovieFile(&movieFSS, 'TVOD', -1, createMovieFileDeleteCurFile, &movieResRef, &theMovie);
  76.     if (err) return;
  77.  
  78.     // make up a 3d track, and media, very quickly
  79.     threeDeeTrack = NewMovieTrack(theMovie, 320 << 16, 240 << 16, 0);        // 320x240 pixels in size
  80.     threeDeeMedia = NewTrackMedia(threeDeeTrack, 'qd3d', 1000, (Handle)alias, rAliasType);        // make up a media that points to the 3dmf file
  81.  
  82.     // add the 3dmf file as a sample to the media (5 seconds long second long)
  83.     err = AddMediaSampleReference(threeDeeMedia, 0, eof, 5000, (SampleDescriptionHandle)sampleDescription,
  84.                 1, 0, nil);
  85.     if (err) return;
  86.  
  87.     // add the 3d media into the track
  88.     InsertMediaIntoTrack(threeDeeTrack, 0, 0, GetMediaDuration(threeDeeMedia), 1L << 16);
  89.  
  90.     // dispose unneeded things
  91.     DisposeHandle((Handle)alias);
  92.     DisposeHandle((Handle)sampleDescription);
  93.  
  94.     // make up a tween track, and media, very quickly
  95.     tweenTrack = NewMovieTrack(theMovie, 0, 0, 0);
  96.     tweenMedia = NewTrackMedia(tweenTrack, TweenMediaType, 1000, (Handle)nil, 0);        // make up a media that stores its data in the movie's file
  97.  
  98.     // make up an empty tween sample
  99.     err = QTNewAtomContainer(&tweenSample);
  100.     if (err) return;
  101.  
  102.     // add a tween entry to tween the camera
  103.     tweenCamera.placement.cameraLocation = cameraFrom;
  104.     tweenCamera.placement.pointOfInterest = cameraTo;
  105.     tweenCamera.placement.upVector = cameraUp;
  106.  
  107.     tweenCamera.range.yon = 1000.0;
  108.     tweenCamera.range.hither = 0.001;
  109.  
  110.     tweenCamera.viewPort.origin.x = -1.0;
  111.     tweenCamera.viewPort.origin.y = 1.0;
  112.     tweenCamera.viewPort.width = 2.0;
  113.     tweenCamera.viewPort.height = 2.0;
  114.  
  115.     err = addTweenEntryToSample(tweenSample, 1, kTweenType3dCameraData, &tweenCamera, sizeof(tweenCamera));
  116.     if (err) return;
  117.  
  118.     tweenCamera.placement.cameraLocation.x *= 5.0;
  119.     tweenCamera.placement.cameraLocation.y *= 5.0;
  120.     tweenCamera.placement.cameraLocation.z *= 5.0;
  121.  
  122.     err = setTweenEntryInitialConditions(tweenSample, 1, &tweenCamera, sizeof(tweenCamera));
  123.     if (err) return;
  124.  
  125.     // make up a tween sample description
  126.     sampleDescription = (ThreeDeeDescriptionHandle)NewHandleClear(sizeof(SampleDescription));
  127.     if (err = MemError()) return;
  128.     (**sampleDescription).descSize = sizeof(SampleDescription);
  129.  
  130.     // add the tween sample to the tween media
  131.     err = BeginMediaEdits(tweenMedia);
  132.     if (err) return;
  133.  
  134.     err = AddMediaSample(tweenMedia, tweenSample, 0, GetHandleSize(tweenSample), 5000, (SampleDescriptionHandle)sampleDescription, 1, 0, nil);
  135.     if (err) return;
  136.  
  137.     err = EndMediaEdits(tweenMedia);
  138.     if (err) return;
  139.  
  140.     // add the tween media into the track
  141.     InsertMediaIntoTrack(tweenTrack, 0, 0, GetMediaDuration(tweenMedia), 1L << 16);
  142.  
  143.     // throw away a few things
  144.     QTDisposeAtomContainer(tweenSample);
  145.     DisposeHandle((Handle)sampleDescription);
  146.  
  147.     // create two links (references) between the 3d and tween tracks
  148.     err = AddTrackReference(threeDeeTrack, tweenTrack, kTrackModifierReference, &referenceIndex1);
  149.     if (err) return;
  150.  
  151.     // create an empty input map for the 3d track
  152.     err = QTNewAtomContainer(&inputMap);
  153.     if (err) return;
  154.  
  155.     err = addTweenEntryToInputMapEntry(inputMap, referenceIndex1, 1, kTrackModifierCameraData, nil);
  156.     if (err) return;
  157.  
  158.     // attach the input map to the 3d media handler
  159.     err = SetMediaInputMap(threeDeeMedia, inputMap);
  160.     if (err) return;
  161.  
  162.     // throw away the input map
  163.     QTDisposeAtomContainer(inputMap);
  164.  
  165.     // add the movie resource to the movie file
  166.     err = AddMovieResource(theMovie, movieResRef, nil, nil);
  167.     if (err) return;
  168.  
  169.     // close the movie file
  170.     CloseMovieFile(movieResRef);
  171.  
  172.     // toss that movie too (automatically tosses all tracks, media, etc).
  173.     DisposeMovie(theMovie);
  174. }
  175.  
  176. OSErr addTweenEntryToSample(QTAtomContainer tweenSample, long tweenID, long tweenType, 
  177.                                 void *tweenData, long tweenDataSize)
  178. {
  179.     OSErr err;
  180.     QTAtom tweenAtom;
  181.  
  182.     // create entry for this tween in the sample
  183.     err = QTInsertChild(tweenSample, kParentAtomIsContainer, kTweenEntry, tweenID, 0, 0, nil, &tweenAtom);
  184.     if (err) goto bail;
  185.  
  186.     // define the type of this tween entry
  187.     err = QTInsertChild(tweenSample, tweenAtom, kTweenType, 1, 0, sizeof(tweenType), &tweenType, nil);
  188.     if (err) goto bail;
  189.  
  190.     // define the data for this tween entry
  191.     err = QTInsertChild(tweenSample, tweenAtom, kTweenData, 1, 0, tweenDataSize, tweenData, nil);
  192.     if (err) goto bail;
  193.  
  194. bail:
  195.     return err;
  196. }
  197.  
  198. OSErr setTweenEntryStartOffset(QTAtomContainer tweenSample, long tweenID, TimeValue startOffset)
  199. {
  200.     QTAtom tweenAtom;
  201.  
  202.     // look up the tween entry
  203.     tweenAtom = QTFindChildByID(tweenSample, kParentAtomIsContainer, kTweenEntry, tweenID, nil);
  204.     if (!tweenAtom)
  205.         return paramErr;
  206.  
  207.     // add in the start offset
  208.     return QTInsertChild(tweenSample, tweenAtom, kTweenStartOffset, 1, 0, sizeof(startOffset), &startOffset, nil);
  209. }
  210.  
  211. OSErr setTweenEntryDuration(QTAtomContainer tweenSample, long tweenID, TimeValue duration)
  212. {
  213.     QTAtom tweenAtom;
  214.  
  215.     // look up the tween entry
  216.     tweenAtom = QTFindChildByID(tweenSample, kParentAtomIsContainer, kTweenEntry, tweenID, nil);
  217.     if (!tweenAtom)
  218.         return paramErr;
  219.  
  220.     // add in the start offset
  221.     return QTInsertChild(tweenSample, tweenAtom, kTweenDuration, 1, 0, sizeof(duration), &duration, nil);
  222. }
  223.  
  224. OSErr setTweenEntryInitialConditions(QTAtomContainer tweenSample, long tweenID,
  225.             void *initialData, long initialDataSize)
  226. {
  227.     QTAtom tweenAtom;
  228.  
  229.     // look up the tween entry
  230.     tweenAtom = QTFindChildByID(tweenSample, kParentAtomIsContainer, kTweenEntry, tweenID, nil);
  231.     if (!tweenAtom)
  232.         return paramErr;
  233.  
  234.     // add in the initial data offset
  235.     return QTInsertChild(tweenSample, tweenAtom, kTween3dInitialCondition, 1, 0, initialDataSize, initialData, nil);
  236. }
  237.  
  238. OSErr addTweenEntryToInputMapEntry(QTAtomContainer inputMap, long referenceIndex, long tweenID,
  239.                 long tweenType, char *name)
  240. {
  241.     OSErr err;
  242.     QTAtom inputAtom;
  243.  
  244.     // add a input entry to the input mape
  245.     err = QTInsertChild(inputMap, kParentAtomIsContainer, kTrackModifierInput, referenceIndex,
  246.                 0, 0, nil, &inputAtom);
  247.     if (err) goto bail;
  248.  
  249.     // set the type of the modifier input (for 3d, this is almost always kTrackModifierType3d4x4Matrix)
  250.     err = QTInsertChild(inputMap, inputAtom, kTrackModifierType, 1, 0, 
  251.                sizeof(tweenType), &tweenType, nil);
  252.     if (err) goto bail;
  253.  
  254.     // set the sub input id (the id of the tween entry)
  255.     err = QTInsertChild(inputMap, inputAtom, kInputMapSubInputID, 1, 0, 
  256.                sizeof(tweenID), &tweenID, nil);
  257.     if (err) goto bail;
  258.  
  259.     // define the name
  260.     if (name) {
  261.         long nameLen = 1;
  262.         Ptr p = name;
  263.  
  264.         while (*p++)
  265.             nameLen++;
  266.  
  267.         err = QTInsertChild(inputMap, inputAtom, kTrackModifierInputName, 1, 0, 
  268.                  nameLen, name, nil);
  269.         if (err) goto bail;
  270.     }
  271.  
  272. bail:
  273.     return err;
  274. }
  275.